package com.chenfan.process.entity.po;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.annotation.TableName;
import com.chenfan.ccp.common.exception.ApiException;
import com.chenfan.ccp.entity.BaseEntity;
import com.chenfan.ccp.plug.mybatis.annotation.Column;
import com.chenfan.ccp.util.tool.JsonUtil;
import com.chenfan.ccp.util.tool.UuidUtil;
import com.chenfan.infra.context.UserContextHolder;
import com.chenfan.infra.vo.UserVO;
import com.chenfan.process.common.exception.ProcessResultCode;
import com.chenfan.process.dto.ApprovalDTO;
import com.chenfan.process.enums.ProcessEnums;
import com.chenfan.process.util.TenantUtil;
import com.chenfan.process.vo.ApprovalVo;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.EqualsAndHashCode;

import java.util.Date;
import java.util.Objects;

/**
 * @author K
 * @date 2021/1/26
 */
@EqualsAndHashCode(callSuper = true)
@Data
@TableName(value = "chenfan_paas_approval_po")
public class ApprovalPo extends BaseEntity<ApprovalPo> {

    @JsonSerialize(using = ToStringSerializer.class)
    private Long id;
    /**
     * 审批ID
     */
    @JsonSerialize(using = ToStringSerializer.class)
    private Long approvalId;

    /**
     * 服务名称
     */
    private String serviceName;

    /**
     * 审批模板ID
     */
    @JsonSerialize(using = ToStringSerializer.class)
    private Long approvalTemplateId;
    /**
     * length = -1 表示为json格式数据
     */
    @Column(commit = "", length = -1)
    private String param;

    /**
     * 流程创建人id
     */
    @JsonSerialize(using = ToStringSerializer.class)
    private Long createBy;

    /**
     * 流程创建人名称
     */
    private String createName;

    /**
     * 更新人id
     */
    @JsonSerialize(using = ToStringSerializer.class)
    private Long updateBy;

    /**
     * 更新人名称
     */
    private String updateName;

    /**
     * 审批状态
     */
    private Integer status;

    /**
     * 当前审批人ID
     */
    private String userId;

    /**
     * 当前审批人名称
     */
    private String userName;

    @ApiModelProperty("当前版本")
    private Long version;

    @ApiModelProperty("租户ID")
    private Long tenantId;

    /**
     * 业务id
     */
    @JsonSerialize(using = ToStringSerializer.class)
    private Long businessId;

    /**
     * 业务code
     */
    private String businessCode;

    @ApiModelProperty("业务待办参数")
    private String businessParam;

    public static final String APPROVAL_ID = "approval_id";
    public static final String SERVICE_NAME = "service_name";
    public static final String USER_ID = "user_id";
    public static final String STATUS = "status";
    public static final String APPROVAL_TEMPLATE_ID = "approval_template_id";
    public static final String VERSION = "version";
    public static final String CREATE_TIME = "create_time";
    public static final String BUSINESS_CODE = "business_code";


    public ApprovalVo copyApprovalVo() {
        ApprovalVo vo = new ApprovalVo();
        org.springframework.beans.BeanUtils.copyProperties(this, vo);
        return vo;
    }

    public static ApprovalPo init(Long approvalId, Long version, ApprovalDTO approval) {
        ApprovalPo approvalPo = new ApprovalPo();
        if (Objects.nonNull(approval.getParam()) && Objects.nonNull(approval.getParam().getParameter())) {

            // 校验格式问题
            String parameter = approval.getParam().getParameter();
            try {
                JsonUtil.string2Obj(parameter, JSONObject.class);
            } catch (Exception e) {
                throw new ApiException(ProcessResultCode.JSON_FORMAT_ERROR);
            }
            approvalPo.setParam(parameter);
        }
        approvalPo.setBusinessId(approval.getBusinessId());
        approvalPo.setBusinessCode(approval.getBusinessCode());
        approvalPo.setBusinessParam(approval.getBusinessParam());
        approvalPo.setApprovalId(UuidUtil.generateId());
        approvalPo.setVersion(version);
        approvalPo.setCreateBy(approval.getUseId());
        approvalPo.setCreateTime(new Date());
        approvalPo.setApprovalTemplateId(approvalId);
        approvalPo.setCreateName(approval.getUserName());
        approvalPo.setStatus(ProcessEnums.APPROVING.getCode());
        approvalPo.setTenantId(TenantUtil.getTenantId());
        return approvalPo;
    }

    public void updateSelf() {
        UserVO userVo = UserContextHolder.getUserVo();
        if (Objects.nonNull(userVo)) {
            setUpdateBy(userVo.getUserId());
            setUpdateName(userVo.getRealName());
        }
        setUpdateTime(new Date());
    }

    public void validate() {
        if (!ProcessEnums.APPROVING.getCode().equals(status)) {
            throw new ApiException(ProcessResultCode.APPROVAL_STATUS_CHANGE);
        }
    }

    public void refuse() {
        setStatus(ProcessEnums.REFUSE.getCode());
        updateSelf();
    }

    public void revoke() {
        setStatus(ProcessEnums.REVOKE.getCode());
        updateSelf();
    }

    public void finish() {
        setStatus(ProcessEnums.FINISH.getCode());
        updateSelf();
    }

    public boolean isFinish() {
        return ProcessEnums.FINISH.getCode().equals(getStatus());
    }

}
